home *** CD-ROM | disk | FTP | other *** search
/ Reverse Code Engineering RCE CD +sandman 2000 / ReverseCodeEngineeringRceCdsandman2000.iso / RCE / Ebooks / Thinking in C++ V2 / C19 / Getmem.h < prev    next >
Encoding:
C/C++ Source or Header  |  2000-05-25  |  1.4 KB  |  51 lines

  1. //: C19:Getmem.h
  2. // From Thinking in C++, 2nd Edition
  3. // Available at http://www.BruceEckel.com
  4. // (c) Bruce Eckel 1999
  5. // Copyright notice in Copyright.txt
  6. // Function template for memory
  7. #ifndef GETMEM_H
  8. #define GETMEM_H
  9. #include "../require.h"
  10. #include <cstdlib>
  11. #include <cstring>
  12.  
  13. template<class T>
  14. void getmem(T*& oldmem, int elems) {
  15.   typedef int cntr; // Type of element counter
  16.   const int csz = sizeof(cntr); // And size
  17.   const int tsz = sizeof(T);
  18.   if(elems == 0) {
  19.     free(&(((cntr*)oldmem)[-1]));
  20.     return;
  21.   }
  22.   T* p = oldmem;
  23.   cntr oldcount = 0;
  24.   if(p) { // Previously allocated memory
  25.     // Old style:
  26.     // ((cntr*)p)--; // Back up by one cntr
  27.     // New style:
  28.     cntr* tmp = reinterpret_cast<cntr*>(p);
  29.     p = reinterpret_cast<T*>(--tmp);
  30.     oldcount = *(cntr*)p; // Previous # elems
  31.   }
  32.   T* m = (T*)realloc(p, elems * tsz + csz);
  33.   require(m != 0);
  34.   *((cntr*)m) = elems; // Keep track of count
  35.   const cntr increment = elems - oldcount;
  36.   if(increment > 0) {
  37.     // Starting address of data:
  38.     long startadr = (long)&(m[oldcount]);
  39.     startadr += csz;
  40.     // Zero the additional new memory:
  41.     memset((void*)startadr, 0, increment * tsz);
  42.   }
  43.   // Return the address beyond the count:
  44.   oldmem = (T*)&(((cntr*)m)[1]);
  45. }
  46.  
  47. template<class T>
  48. inline void freemem(T * m) { getmem(m, 0); }
  49.  
  50. #endif // GETMEM_H ///:~
  51.